package qp.src.app.client;


import java.util.List;

import qp.src.app.shared.DataBeanProxy;
import qp.src.app.shared.DataGridRequestFactory;
import qp.src.app.shared.EntityRequest;

import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.core.client.GWT;
import com.google.gwt.event.shared.EventBus;
import com.google.gwt.event.shared.SimpleEventBus;
import com.google.gwt.user.cellview.client.DataGrid;
import com.google.gwt.user.client.ui.RootPanel;
import com.google.gwt.user.client.ui.VerticalPanel;
import com.google.web.bindery.requestfactory.shared.EntityProxyChange;
import com.google.web.bindery.requestfactory.shared.EntityProxyId;
import com.google.web.bindery.requestfactory.shared.Receiver;
import com.google.web.bindery.requestfactory.shared.WriteOperation;


public class DataGridX<C, T> implements EntryPoint {

  private DataGridUi dataGridUi;
  private DataGrid<DataBeanProxy> dataGrid;
  private EventBus eventBus;
  private DataGridRequestFactory factory;
  private EntityRequest entityRequest;

  public void onModuleLoad() {
    GWT.setUncaughtExceptionHandler(new CustomUncaughtExceptionHandler());
    factory = GWT.create(DataGridRequestFactory.class);
    /*********************    INTI RF     *******************/
    eventBus = new SimpleEventBus();
    factory.initialize(eventBus);

    /*********************    UI    ****************/
    dataGridUi = new DataGridUi(factory);
    init();
    dataGrid = dataGridUi.getDataGrid();

    /*********************    RF    ****************/
    EntityProxyChange.registerForProxyType(eventBus,
        DataBeanProxy.class,
        CHANGE_PROXY_HANDLER
    );
    entityRequest = factory.entityRequest();
    entityRequest.getDataBean().with("data").fire(new Receiver<List<DataBeanProxy>>() {

      @Override
      public void onSuccess(List<DataBeanProxy> response) {
        System.out.println("SUBDATA = "+response.get(0).getData());
        dataGridUi.setData( response );
      }
    });
  }

  private EntityProxyChange.Handler<DataBeanProxy> CHANGE_PROXY_HANDLER = new
  EntityProxyChange.Handler<DataBeanProxy>() {

    @Override
    public void onProxyChange(EntityProxyChange<DataBeanProxy> event) {
      if( WriteOperation.PERSIST.equals(event.getWriteOperation()) ){
        EntityProxyId<DataBeanProxy> id = event.getProxyId();
        factory.find(id).with("data").fire(new Receiver<DataBeanProxy>() {
          @Override
          public void onSuccess(DataBeanProxy reProxy) {
            dataGridUi.addDataToGrid(reProxy);
          }
        });
      }
      else if( WriteOperation.UPDATE.equals(event.getWriteOperation()) ){
        EntityProxyId<DataBeanProxy> id = event.getProxyId();
        int displayOffset = offsetOf(id);
        if (displayOffset != -1) {
          factory.find(id).with("data").fire(new Receiver<DataBeanProxy>() {
            @Override
            public void onSuccess(DataBeanProxy reProxy) {
              dataGridUi.updateDataToGrid(reProxy);
            }
          });
        }
      }
      else if( WriteOperation.DELETE.equals( event.getWriteOperation()) ){
        dataGridUi.removeDataToGrid( event.getProxyId() );
      }
    }
  };

  /**
   *  Check data is in grid
   */
  private int offsetOf(EntityProxyId<DataBeanProxy> dataBeanProxy) {
    List<DataBeanProxy> displayedItems = dataGrid.getVisibleItems();
    for (int offset = 0; offset < displayedItems.size(); offset++) {
      if (dataBeanProxy.equals(displayedItems.get(offset).stableId())) {
        return offset;
      }
    }
    return -1;
  }

  private void init(){
    VerticalPanel [] panels = dataGridUi.init();

    RootPanel.get("left_menu").add(panels[0]);
    RootPanel.get("content_page").add(panels[1]);
  }

}
